#!/bin/bash
yum_repo_list_altarch=(
    "阿里云@https://mirrors.wlnmp.com/centos/Centos7-aliyun-altarch.repo"
    "网易@https://mirrors.wlnmp.com/centos/Centos7-163-altarch.repo"
    "腾讯云@https://mirrors.wlnmp.com/centos/Centos7-tencent-altarch.repo"
    "中科大@https://mirrors.wlnmp.com/centos/Centos7-ustc-altarch.repo"
    "荆楚理工学院@https://mirrors.wlnmp.com/centos/Centos7-jcut-altarch.repo"
    "清华大学@https://mirrors.wlnmp.com/centos/Centos7-tuna-altarch.repo"
    "南阳理工学院@https://mirrors.wlnmp.com/centos/Centos7-nyist-altarch.repo"
)

## YUM x86_64 repo list
yum_repo_list_x86_64=(
    "阿里云@https://mirrors.wlnmp.com/centos/Centos7-aliyun-x86_64.repo"
    "网易@https://mirrors.wlnmp.com/centos/Centos7-163-x86_64.repo"
    "腾讯云@https://mirrors.wlnmp.com/centos/Centos7-tencent-x86_64.repo"
    "中科大@https://mirrors.wlnmp.com/centos/Centos7-ustc-x86_64.repo"
    "荆楚理工学院@https://mirrors.wlnmp.com/centos/Centos7-jcut-x86_64.repo"
    "清华大学@https://mirrors.wlnmp.com/centos/Centos7-tuna-x86_64.repo"
    "南阳理工学院@https://mirrors.wlnmp.com/centos/Centos7-nyist-x86_64.repo"
)

## Docker CE software mirror list
mirror_list_docker_ce=(
    "阿里云@mirrors.aliyun.com/docker-ce"
    "腾讯云@mirrors.tencent.com/docker-ce"
    "华为云@mirrors.huaweicloud.com/docker-ce"
    "网易@mirrors.163.com/docker-ce"
    "清华大学@mirrors.tuna.tsinghua.edu.cn/docker-ce"
    "中科大@mirrors.ustc.edu.cn/docker-ce"
    "官方@download.docker.com"
)

## Docker Registry mirror list
mirror_list_registry=(
    "毫秒镜像@docker.1ms.run"
    "DaoCloud 道客@docker.m.daocloud.io"
    "Docker Proxy@dockerproxy.net"
    "阿里云（杭州）@registry.cn-hangzhou.aliyuncs.com"
    "腾讯云@mirror.ccs.tencentyun.com"
    "网易@hub-mirror.c.163.com"
    "1Panel 镜像@docker.1panel.live"
)

## Directories and Files
Dir_YumRepos=/etc/yum.repos.d
Dir_YumReposBackup=$Dir_YumRepos/bak
Dir_Docker=/etc/docker
File_DockerConfig=$Dir_Docker/daemon.json
File_DockerConfigBackup=$Dir_Docker/daemon.json.bak

## Colors and Styles
RED='\033[31m'
GREEN='\033[32m'
YELLOW='\033[33m'
BLUE='\033[34m'
PLAIN='\033[0m'
BOLD='\033[1m'
SUCCESS="\033[1;32m✔${PLAIN}"
ERROR="\033[1;31m✘${PLAIN}"
WORKING="\033[1;36m◉${PLAIN}"

function run_start() {
    clear
    echo -e "+-------------------------------------------------+"
    echo -e "| \033[0;1;35;95m⡇\033[0m  \033[0;1;33;93m⠄\033[0m \033[0;1;32;92m⣀⡀\033[0m \033[0;1;36;96m⡀\033[0;1;34;94m⢀\033[0m \033[0;1;35;95m⡀⢀\033[0m \033[0;1;31;91m⡷\033[0;1;33;93m⢾\033[0m \033[0;1;32;92m⠄\033[0m \033[0;1;36;96m⡀⣀\033[0m \033[0;1;34;94m⡀\033[0;1;35;95m⣀\033[0m \033[0;1;31;91m⢀⡀\033[0m \033[0;1;33;93m⡀\033[0;1;32;92m⣀\033[0m \033[0;1;36;96m⢀⣀\033[0m  |"
    echo -e "| \033[0;1;31;91m⠧\033[0;1;33;93m⠤\033[0m \033[0;1;32;92m⠇\033[0m \033[0;1;36;96m⠇⠸\033[0m \033[0;1;34;94m⠣\033[0;1;35;95m⠼\033[0m \033[0;1;31;91m⠜⠣\033[0m \033[0;1;33;93m⠇\033[0m \033[0;1;32;92m⠸\033[0m \033[0;1;36;96m⠇\033[0m \033[0;1;34;94m⠏\033[0m  \033[0;1;35;95m⠏\033[0m  \033[0;1;33;93m⠣⠜\033[0m \033[0;1;32;92m⠏\033[0m  \033[0;1;34;94m⠭⠕\033[0m  |"
    echo -e "+-------------------------------------------------+"
    echo -e "  欢迎使用 CentOS 7 YUM 源与 Docker 环境一键配置脚本"
    echo -e ''
}

function show_menu() {
    run_start
    echo -e "  请选择要执行的操作:"
    echo -e "  -------------------------------------------------"
    echo -e "    ${GREEN}1.${PLAIN}  一键配置 YUM 源"
    echo -e "    ${GREEN}2.${PLAIN}  一键安装 Docker 并配置镜像源"
    echo -e "  -------------------------------------------------"
    echo
}

function main() {
    permission_judgment
    collect_system_info

    while true; do
        show_menu
        read -p "  请输入您的选择 [1-2]，或按 Ctrl+C 退出: " choice
        case $choice in
            1)
                configure_yum_repo
                echo -e "\n${SUCCESS} YUM 源配置任务已完成！"
                break
                ;;
            2)
                echo -e "\n${YELLOW}提示: Docker 安装依赖于一个可用的 YUM 源。如果 YUM 源配置不正确，此步骤可能会失败。${PLAIN}"
                sleep 2
                install_docker_suite
                configure_docker_mirror
                check_installed_result
                break
                ;;
            *)
                echo -e "\n${ERROR} 无效输入，请输入 1 或 2。"
                sleep 2
                ;;
        esac
    done

    run_end
}

function run_end() {
    echo -e "\n✨ 脚本运行完毕！"
}

function output_error() {
    [ "$1" ] && echo -e "\n$ERROR $1\n"
    exit 1
}

function command_exists() {
    command -v "$@" &>/dev/null
}

function permission_judgment() {
    if [ $UID -ne 0 ]; then
        output_error "权限不足，请使用 Root 用户运行本脚本"
    fi
}

function collect_system_info() {
    if [ ! -f /etc/redhat-release ]; then
        output_error "此脚本仅适用于 CentOS 7 系统。"
    fi
    local centos_major_version
    centos_major_version=$(grep -oE '[0-9]+' /etc/redhat-release | head -n1)
    if [ "$centos_major_version" != "7" ]; then
        output_error "检测到您的系统为 CentOS ${centos_major_version}，此脚本仅适用于 CentOS 7。"
    fi
    DEVICE_ARCH_RAW="$(uname -m)"
}

function animate_exec() {
    local cmd="$1"
    local title="$2"
    local temp_file
    temp_file=$(mktemp)
    
    local spinner_frames=("⠋" "⠙" "⠹" "⠸" "⠼" "⠴" "⠦" "⠧" "⠇" "⠏")
    
    eval "${cmd}" >"${temp_file}" 2>&1 &
    local cmd_pid=$!
    
    local spin_idx=0
    while kill -0 $cmd_pid 2>/dev/null; do
        spin_idx=$(((spin_idx + 1) % ${#spinner_frames[@]}))
        echo -ne "\r${WORKING} ${title} [${BLUE}${spinner_frames[$spin_idx]}${PLAIN}]"
        sleep 0.1
    done
    
    wait $cmd_pid
    local exit_status=$?
    
    if [ $exit_status -eq 0 ]; then
        echo -e "\r${SUCCESS} ${title} [${GREEN}成功${PLAIN}]  "
    else
        echo -e "\r${ERROR} ${title} [${RED}失败${PLAIN}]  "
        echo -e "\n---错误日志---"
        cat "${temp_file}"
        echo -e "---错误日志---\n"
    fi
    
    rm -f "${temp_file}"
    return $exit_status
}

function configure_yum_repo() {
    echo -e "${WORKING} 正在开始配置 YUM 源..."
    
    if [ -d "$Dir_YumReposBackup" ]; then
        echo -e "${YELLOW}检测到已存在的备份目录 ${Dir_YumReposBackup}，跳过备份。${PLAIN}"
    else
        mkdir -p "$Dir_YumReposBackup"
        if [ "$(ls -A $Dir_YumRepos/*.repo 2>/dev/null)" ]; then
            mv $Dir_YumRepos/*.repo "$Dir_YumReposBackup/"
            echo -e "${SUCCESS} 已备份原有 YUM 源至 ${Dir_YumReposBackup}"
        else
            echo -e "${YELLOW}未找到 YUM 配置文件，无需备份。${PLAIN}"
        fi
    fi

    local yum_repo_list_name
    if [[ "${DEVICE_ARCH_RAW}" == "x86_64" ]]; then
        yum_repo_list_name="yum_repo_list_x86_64"
    else
        yum_repo_list_name="yum_repo_list_altarch"
    fi

    local successful_yum_config=false
    local repo_list_sum
    repo_list_sum=$(eval echo \${#$yum_repo_list_name[@]})

    for ((i = 0; i < $repo_list_sum; i++)); do
        local repo_info
        repo_info=$(eval echo \${${yum_repo_list_name}[$i]})
        local repo_name="${repo_info%@*}"
        local repo_url="${repo_info#*@}"
        local repo_filename
        repo_filename=$(basename "$repo_url")

        echo -e "\n${WORKING} 正在尝试使用 ${BOLD}${repo_name}${PLAIN} 源 (${repo_url})..."
        if ! animate_exec "curl -L --fail -o $Dir_YumRepos/$repo_filename $repo_url" "下载 ${repo_name} 配置文件"; then
            rm -f "$Dir_YumRepos/$repo_filename"
            continue
        fi

        yum clean all &>/dev/null
        if animate_exec "yum makecache" "生成 ${repo_name} 源缓存"; then
            successful_yum_config=true
            echo -e "${SUCCESS} YUM 源 ${BOLD}${repo_name}${PLAIN} 配置成功！"
            break
        else
            rm -f "$Dir_YumRepos/$repo_filename"
        fi
    done

    if [ "$successful_yum_config" = false ]; then
        output_error "所有 YUM 源都尝试失败，请检查您的网络连接或服务器DNS设置。"
    fi
}

function install_docker_suite() {
    echo -e "\n${WORKING} 正在开始安装 Docker..."

    animate_exec "yum remove -y docker docker-client docker-client-latest docker-common docker-latest docker-latest-logrotate docker-logrotate docker-engine" "卸载旧版本 Docker (如有)"
    
    if ! animate_exec "yum install -y yum-utils device-mapper-persistent-data lvm2" "安装 Docker 依赖包"; then
        output_error "依赖包安装失败，请检查 YUM 源配置。"
    fi
    
    local successful_docker_repo=false
    if [ -f "/etc/yum.repos.d/docker-ce.repo" ]; then
        rm -f /etc/yum.repos.d/docker-ce.repo
    fi
    
    for ce_mirror_info in "${mirror_list_docker_ce[@]}"; do
        local ce_mirror_name="${ce_mirror_info%@*}"
        local ce_mirror_url="${ce_mirror_info#*@}"

        echo -e "\n${WORKING} 正在尝试使用 ${BOLD}${ce_mirror_name}${PLAIN} Docker CE 源..."
        if ! animate_exec "yum-config-manager --add-repo https://${ce_mirror_url}/linux/centos/docker-ce.repo" "添加 ${ce_mirror_name} 源仓库"; then
            rm -f /etc/yum.repos.d/docker-ce.repo
            continue
        fi

        sed -i "s|download.docker.com|${ce_mirror_url}|g" /etc/yum.repos.d/docker-ce.repo
        
        yum clean all &>/dev/null
        if animate_exec "yum makecache" "生成 ${ce_mirror_name} Docker CE 源缓存"; then
            successful_docker_repo=true
            echo -e "${SUCCESS} Docker CE 源 ${BOLD}${ce_mirror_name}${PLAIN} 配置成功！"
            break
        else
            rm -f /etc/yum.repos.d/docker-ce.repo
        fi
    done

    if [ "$successful_docker_repo" = false ]; then
        output_error "所有 Docker CE 源都尝试失败，无法继续安装。"
    fi

    if ! animate_exec "yum install -y docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin" "安装最新版 Docker Engine"; then
        output_error "Docker Engine 安装失败，请检查YUM源或网络。"
    fi
    
    animate_exec "systemctl enable --now docker" "启动并设置 Docker 开机自启"
}

function configure_docker_mirror() {
    echo -e "\n${WORKING} 正在配置 Docker Registry 加速镜像..."

    if [ -f "$File_DockerConfig" ]; then
        if [ ! -f "$File_DockerConfigBackup" ]; then
            cp "$File_DockerConfig" "$File_DockerConfigBackup"
            echo -e "${SUCCESS} 已备份原有 Docker 配置文件至 ${File_DockerConfigBackup}"
        else
             echo -e "${YELLOW}检测到已存在的备份文件，跳过备份。${PLAIN}"
        fi
    else
        mkdir -p "$Dir_Docker"
    fi

    local successful_mirror=false
    for mirror_info in "${mirror_list_registry[@]}"; do
        local mirror_name="${mirror_info%@*}"
        local mirror_url="${mirror_info#*@}"
        
        echo -e "\n${WORKING} 正在尝试使用 ${BOLD}${mirror_name}${PLAIN} 加速源 (${mirror_url})..."
        
        echo -e '{\n  "registry-mirrors": ["https://'"${mirror_url}"'"]\n}' > "$File_DockerConfig"
        
        systemctl daemon-reload
        if ! animate_exec "systemctl restart docker" "重启 Docker 服务"; then
            continue
        fi
        
        if animate_exec "timeout 60s docker pull hello-world" "拉取测试镜像"; then
            successful_mirror=true
            echo -e "${SUCCESS} Docker 加速源 ${BOLD}${mirror_name}${PLAIN} 配置成功！"
            animate_exec "docker rmi hello-world" "清理测试镜像" &>/dev/null
            break
        fi
    done
    
    if [ "$successful_mirror" = false ]; then
        echo -e "\n${YELLOW}所有 Docker 加速源均超时或失败。您可以尝试手动配置或检查网络。${PLAIN}"
    fi
}

function check_installed_result() {
    if command_exists docker; then
        echo -en "\n${SUCCESS} Docker 已成功安装！当前版本信息：\n"
        docker -v
        docker compose version
        echo ''
        if [[ $(systemctl is-active docker) != "active" ]]; then
           echo -e "\n$ERROR 检测到 Docker 服务未运行，请手动执行 'systemctl start docker' 进行排查。"
        else
           echo -e "${SUCCESS} Docker 服务正在运行中。"
        fi
    else
        output_error "安装失败，未找到 'docker' 命令。"
    fi
}

# Run main function
main